
#pragma comment(lib,"user32.lib")

#include<Windows.h>
#include<TlHelp32.h>
#include <iostream>
#include"../mem_op2/mem_util.h"

using namespace std;

class A{
public:
    void f(){
        throw "Exception";
    }
    virtual ~A(){
        cout << "A Over!" << endl;
    }
};

void exit_end(){
    cout << "exit system"<<endl;

}

HHOOK hHook;

LRESULT CALLBACK HookProc(int nCode,WPARAM wParam,LPARAM lParam){
    if(nCode == HC_ACTION){
        cout << "HookProc execute" << endl;
    }
    cout << "HookProc execute" << endl;
    return CallNextHookEx(hHook,nCode,wParam,lParam);
}

int main()
{


    hHook = SetWindowsHookEx(WH_CALLWNDPROC,HookProc,GetModuleHandle(NULL),0);

    cout << "Hello World!" << endl;

    try {
        A a;
        a.f();
    } catch (const char *s) {
        cout << s << endl;
    }

    atexit(exit_end);

    HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0);
    if(hSnapshot != INVALID_HANDLE_VALUE){
        PROCESSENTRY32 pe32;
        pe32.dwSize = sizeof (PROCESSENTRY32);
        if(Process32First(hSnapshot,&pe32)){
            do {
                wcout << "process exefile:" << pe32.szExeFile
                     << "\t\tPID: " << pe32.th32ProcessID << endl;

            } while (Process32Next(hSnapshot,&pe32));
        }

        CloseHandle(hSnapshot);
    }

    cout << "messagebox address: " << MessageBoxA << endl;


    UnhookWindowsHookEx(hHook);

    unsigned char code[]={0xE8,0x0F,0x13,0xD7,0x76};

    DWORD processid = 0;

    cout << "processid: " ;
    cin >> processid;

    xy::OtherProcess p(processid);

    xy::OtherProcessMemory pm(&p);

    xy::File f(L"D:\\programming\\C++\\mem_ops\\callmessagebox");

    cout << "file size:" << f.size() << endl;

    unsigned char code_s[1024];


    LPVOID addr = pm.alloc(sizeof (code_s));

    cout <<"read code data size: " << f.read(code_s,sizeof (code_s)) << endl;
    pm.write(addr,code_s,sizeof (code_s));
    xy::RemoteThread rt(&p,(LPTHREAD_START_ROUTINE)addr);

    rt.start();

    rt.wait();


    pm.free(addr);

    cout << "remote call over!" << endl;

    return 0;
}
